package draw.common.util;

import com.fasterxml.jackson.databind.JavaType;
import com.fasterxml.jackson.databind.ObjectMapper;
import draw.common.exception.JsonException;
import lombok.Getter;

import java.util.List;
import java.util.concurrent.Callable;

/**
 * json序列化工具
 * 将jackson给封装下
 */
@Getter
public class SerializeUtil {

    private final static ObjectMapper objectMapper = new ObjectMapper();

    private SerializeUtil() {

    }

    private static <T> T tryParse(Callable<T> callable) {
        return tryParse(callable, JsonException.class);
    }

    private static <T> T tryParse(Callable<T> callable, Class<? extends Exception> exceptionClass) {
        try {
            return callable.call();
        } catch (Exception e) {
            //这个是看子类或者他的实现类是这个异常
            if (exceptionClass.isAssignableFrom(e.getClass())) {
                throw new JsonException();
            }
            throw new RuntimeException(e);
        }
    }

    public static String encode(Object obj) {
        return SerializeUtil.tryParse(() -> {
            return objectMapper.writeValueAsString(obj);
        });
    }

    public static <T> T unEncode(String json, Class<T> clazz) {
        return tryParse(() -> {
            return objectMapper.readValue(json, clazz);
        });
    }

    /**
     * 对数组序列化和反序列化
     */
    public static String encode(List<Object> obj) {
        return tryParse(() -> {
            return objectMapper.writeValueAsString(obj);
        });
    }

    public static <T> T unEncodeList(String json, Class<?> clazz) {
        //是通过javaType来序列化数组的
        JavaType javaType = objectMapper
                .getTypeFactory().constructParametricType(List.class, clazz);

        return tryParse(() -> {
            return objectMapper.readValue(json, javaType);
        });
    }

}
